package nl.cwi.arne.generator.tools;

import nl.cwi.arne.Edge;
import nl.cwi.arne.Network;
import nl.cwi.arne.Node;
import nl.cwi.arne.factory.ArneFactory;
import nl.cwi.arne.generator.NetworkActivationGenerator;
import nl.cwi.arne.util.NetworkActivationBuffer;

import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.NullProgressMonitor;
import org.eclipse.equinox.app.IApplicationContext;

/**
 * 
 * The output of this tool is:
 * 
 * 	1		1		1		1		1	
 * 	3		6		20		168		7581	
 * 	6		20		168		7581	
 * 	10		50		887	
 * 	15		105		3490	
 * 	21		196		11196	
 * 	28		336		30900	
 * 	36		540		75966	
 * 	45		825		170379	
 * 	55		1210	
 * 	66		1716	
 * 	78		2366	
 * 	91		3185	
 * 	105		4200	
 * 
 * @author koehler
 *
 */
public class MonotonicityTestTool extends AbstractGeneratorTool {
	
	/*
	 * (non-Javadoc)
	 * @see org.eclipse.equinox.app.IApplication#start(org.eclipse.equinox.app.IApplicationContext)
	 */
	@Override
	public Object start(IApplicationContext context) throws Exception {
		
		NetworkActivationGenerator generator = new NetworkActivationGenerator();
		generator.setMCRL2Options(getMCRL2Options());
		IProgressMonitor monitor = new NullProgressMonitor();
		
		for (byte n=1; n<15; n++) {
			for (byte p=1; p<6; p++) {
				if ((p>2 && n>9) || (p>3 && n>4) || (p>4 && n>3)) continue;
				Network network = createNetwork(p, n);
				generator.generate(network, new NetworkActivationBuffer(network), monitor);
				System.out.print(network.getActivations().size() + "\t");
			}
			System.out.println();
		}
		return null;
	}

	
	private Network createNetwork(byte p, byte n) {
		
		Network network = ArneFactory.eINSTANCE.createNetwork();
		Node node = ArneFactory.eINSTANCE.createNode();
		node.setName("a");
		node.setLevels(n);
		node.setMonotonic(true);
		network.getNodes().add(node);
		
		for (byte i=0; i<p; i++) {
			Node other = ArneFactory.eINSTANCE.createNode();
			other.setName(String.valueOf((char) 'b'+i));
			other.setLevels((byte) 1);
			network.getNodes().add(other);
			Edge edge = ArneFactory.eINSTANCE.createEdge();
			edge.setSource(other);
			edge.setTarget(node);
			network.getEdges().add(edge);
		}
		
		return network;
		
	}
	
}
